package com.example.demo.saToken.controller;

import cn.dev33.satoken.annotation.SaCheckRole;
import cn.dev33.satoken.stp.StpUtil;
import cn.dev33.satoken.util.SaResult;
import cn.hutool.log.Log;
import cn.hutool.log.LogFactory;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import org.springframework.web.bind.annotation.*;

/**
 * @ClassName AdminUserController
 * @Description 管理员用户管理控制器（踢出用户、强制下线等管理员功能）
 * @Author System
 * @Date 2025/9/25
 **/
@RestController
@RequestMapping("/admin/user")
@Tag(name = "管理员用户管理", description = "管理员对用户进行踢出、强制下线等管理操作")
public class AdminUserController {
    
    private static final Log log = LogFactory.get();

    @PostMapping("/logout/{userId}")
    @Operation(summary = "强制用户退出", description = "管理员强制指定用户退出登录")
    @SaCheckRole("admin") // 需要管理员角色
    public SaResult forceLogout(
            @Parameter(description = "用户ID", required = true)
            @PathVariable Long userId) {
        try {
            StpUtil.logout(userId);
            log.info("管理员强制用户退出登录，用户ID: {}, 操作者: {}", userId, StpUtil.getLoginId());
            return SaResult.ok("用户已强制退出登录");
        } catch (Exception e) {
            log.error("强制用户退出失败，用户ID: {}, 错误: {}", userId, e.getMessage());
            return SaResult.error("操作失败: " + e.getMessage());
        }
    }

    @PostMapping("/kickout/{userId}")
    @Operation(summary = "踢出用户", description = "管理员踢出指定用户（强制下线）")
    @SaCheckRole("admin") // 需要管理员角色
    public SaResult kickoutUser(
            @Parameter(description = "用户ID", required = true)
            @PathVariable Long userId) {
        try {
            StpUtil.kickout(userId);
            log.info("管理员踢出用户，用户ID: {}, 操作者: {}", userId, StpUtil.getLoginId());
            return SaResult.ok("用户已被踢出");
        } catch (Exception e) {
            log.error("踢出用户失败，用户ID: {}, 错误: {}", userId, e.getMessage());
            return SaResult.error("操作失败: " + e.getMessage());
        }
    }

    @PostMapping("/kickout-by-token")
    @Operation(summary = "根据Token踢出用户", description = "管理员根据Token值踢出用户")
    @SaCheckRole("admin") // 需要管理员角色
    public SaResult kickoutByToken(
            @Parameter(description = "用户Token", required = true)
            @RequestParam String token) {
        try {
            StpUtil.kickoutByTokenValue(token);
            log.info("管理员根据Token踢出用户，Token: {}, 操作者: {}", token, StpUtil.getLoginId());
            return SaResult.ok("用户已被踢出");
        } catch (Exception e) {
            log.error("根据Token踢出用户失败，Token: {}, 错误: {}", token, e.getMessage());
            return SaResult.error("操作失败: " + e.getMessage());
        }
    }

    @GetMapping("/online-users")
    @Operation(summary = "获取在线用户列表", description = "管理员查看当前在线用户列表")
    @SaCheckRole("admin") // 需要管理员角色
    public SaResult getOnlineUsers() {
        try {
            // 获取所有在线用户的Token信息
            var onlineUsers = StpUtil.searchTokenValue("", 0, -1, false);
            log.info("管理员查询在线用户，操作者: {}, 在线用户数: {}", StpUtil.getLoginId(), onlineUsers.size());
            return SaResult.data(onlineUsers).setMsg("获取在线用户成功");
        } catch (Exception e) {
            log.error("获取在线用户失败，错误: {}", e.getMessage());
            return SaResult.error("获取在线用户失败: " + e.getMessage());
        }
    }
}
